﻿using JWT;
using JWT.Algorithms;
using JWT.Exceptions;
using JWT.Serializers;

namespace Easy.Common.Helper.JWT
{
    /// <summary>
    /// Jwt帮助类
    /// </summary>
    public class JwtHelper
    {
        /// <summary>
        /// 加密Jwt
        /// </summary>
        /// <param name="tokenModel"></param>
        /// <returns></returns>
        public static string EncodeJwt(TokenModelJwt tokenModel)
        {
            double exp = (DateTime.UtcNow.AddSeconds(300) - new DateTime(1970, 1, 1)).TotalSeconds;
            //double exp = (DateTime.UtcNow.AddMinutes(10) - new DateTime(1970, 1, 1)).TotalMinutes;
            var payload = new Dictionary<string, object>
            {
               { "Id",tokenModel.Id },
               { "UserName",tokenModel.UserName },
               { "Avatar",tokenModel.Avatar },
               { "Exp",exp}
            };
            var secret = "www.?@.cn";
            IJwtAlgorithm algorithm = new HMACSHA256Algorithm();
            IJsonSerializer serializer = new JsonNetSerializer();
            IBase64UrlEncoder urlEncoder = new JwtBase64UrlEncoder();
            IJwtEncoder encoder = new JwtEncoder(algorithm, serializer, urlEncoder);
            var token = encoder.Encode(payload, secret);
            return token;
        }


        /// <summary>
        /// 解析Jwt
        /// </summary>
        /// <param name="jwtStr"></param>
        /// <returns></returns>
        public static TokenModelJwt DecodeJwt(string jwtStr)
        {
            var secret = "www.?@.cn";
            try
            {
                IJwtAlgorithm algorithm = new HMACSHA256Algorithm();
                IJsonSerializer serializer = new JsonNetSerializer();
                IDateTimeProvider provider = new UtcDateTimeProvider();
                IJwtValidator validator = new JwtValidator(serializer, provider);
                IBase64UrlEncoder urlEncoder = new JwtBase64UrlEncoder();
                IJwtDecoder decoder = new JwtDecoder(serializer, validator, urlEncoder, algorithm);
                var json = decoder.Decode(jwtStr, secret, verify: true);
                return JsonHelper.JsonToObject<TokenModelJwt>(json);

            }
            catch (TokenExpiredException)
            {
                throw new Exception("Token has expired");
            }
            catch (SignatureVerificationException)
            {
                throw new Exception("Token has invalid signature");
            }
        }
    }

    /// <summary>
    /// 令牌Model
    /// </summary>
    public class TokenModelJwt
    {
        /// <summary>
        /// Id
        /// </summary>
        public long Id { get; set; }
        /// <summary>
        /// 用户名
        /// </summary>
        public string UserName { get; set; }
        /// <summary>
        /// 头像
        /// </summary>
        public string Avatar { get; set; }
    }
}
